import React, { useRef, useEffect, useState } from "react"
import Taro, { useShareAppMessage, useRouter, useDidShow } from "@tarojs/taro"
import {
  GridView,
  Image,
  NestedScrollBody,
  NestedScrollHeader,
  ScrollView,
  StickyHeader,
  StickySection,
  Text,
  View
} from "@tarojs/components"
import { NAVIGATION_BASE_LAYOUT, useNavigationOpacity, useSetState } from "@/utils/hooks"
import GpContainer from "@/components/GpContainer"
import GpShareButton from "@/components/GpShareButton"
import clsx from "clsx"
import GpActionSheet from "@/components/GpActionSheet"
import GpNoteItem from "../../note/components/GpNoteItem"
import styles from "./index.module.scss"
import {
  concernPerson,
  getPersonalPageCollectedNoteList,
  getPersonalPageInfo,
  getPersonalPageNoteList,
  removeMyNote
} from "@/apis/yikao-community"
import { requestIsFullfilled } from "@/utils/request"
import { navigation } from "@/utils/router"
import { pageMapper, pageMapperCommunity } from "@/constants/pageMap"
import { authActionHandler } from "@/utils/app"
import GpNavbar from "@/components/GpNavbar"
import { isSkyline } from "@/utils/core"
import { ScrollViewProps } from "@tarojs/components/types/ScrollView"
import Icon from "@/components/GpFontIcon"
import GpEmpty from "@/components/GpEmpty"

type IState = {
  currentFilter: number
  openAction: boolean
  personalInfo: IApiRelative.IGetPersonalPageInfo.IResData
  list: IApiRelative.IGetPersonalPageNoteList.IGetPersonalPageNoteListItem[]
  hasMore: boolean
  current: number
  isAgency: boolean
  /** 渲染后端是否为skyline */
  skyline: boolean
}
type IParams = {
  /** 当前主页所属访客id, 即是谁的主页 */
  id: string
}
export default function MainPage() {
  const router = useRouter<IParams>()
  const actions = [
    {
      name: "编辑",
      value: "edit"
    },
    {
      name: "删除",
      value: "delete",
      danger: true
    }
  ]
  const [layout, setLayout] = useState<NavigationBaseLayout>(NAVIGATION_BASE_LAYOUT)
  const tabFilters = useRef<IOptionLike<number>[]>([
    { value: 0, label: "笔记" },
    { value: 1, label: "收藏" }
  ])
  const [state, setState, stateRef] = useSetState<IState>(
    {
      currentFilter: tabFilters.current[0].value,
      openAction: false,
      personalInfo: {} as any,
      list: [],
      hasMore: false,
      current: 1,
      isAgency: false,
      skyline: isSkyline()
    },
    true
  )
  const [opacity, scrollHandler] = useNavigationOpacity(state.skyline)
  const currentTargetRef = useRef<INullable<PrimaryKey<number>>>(null)
  /** 是否正在获取,用于在onShow中避免频繁触发获取数据 */
  const isFetching = useRef<boolean>(false)
  useShareAppMessage(() => {
    return {}
  })
  function handleReachBottom() {
    if (stateRef.current!.hasMore) {
      setState({ current: stateRef.current!.current + 1 })
      fetchList()
    }
  }
  useEffect(() => {
    fetchPersonalInfo().then(fetchList)
  }, [])
  useDidShow(() => {
    if (isFetching.current) return
    fetchPersonalInfo().then(() => {
      setState({ current: 1 })
      fetchList()
    })
  })
  function fetchPersonalInfo() {
    isFetching.current = true
    return getPersonalPageInfo({ miniVisitorId: Number(router.params.id) })
      .then(res => {
        if (requestIsFullfilled(res)) {
          const isAgency = res.data.data.agencyId > 0
          if (!res.data.data.isSelf) {
            tabFilters.current[0].label = "最热"
            tabFilters.current[1].label = "最新"
          }
          setState({ personalInfo: res.data.data, isAgency })
        }
        isFetching.current = false
      })
      .catch(() => {
        isFetching.current = false
      })
  }
  function fetchList() {
    isFetching.current = true
    let action: ReturnType<typeof getPersonalPageNoteList>
    if (stateRef.current!.personalInfo.isSelf) {
      // 自己主页, filters: 我的笔记和我收藏的笔记
      if (stateRef.current!.currentFilter === 0) {
        // 我的笔记
        action = getPersonalPageNoteList(
          {
            miniVisitorId: Number(router.params.id)
          },
          {
            pagination: {
              pageSize: 10,
              current: stateRef.current!.current
            },
            sort: {
              predicate: "",
              reverse: false
            },
            search: {}
          }
        )
      } else {
        // 我收藏的笔记
        action = getPersonalPageCollectedNoteList({
          pagination: {
            pageSize: 10,
            current: stateRef.current!.current
          },
          sort: {
            predicate: "",
            reverse: false
          },
          search: {}
        })
      }
    } else {
      // 他人主页, filters: 最热笔记和最新笔记
      action = getPersonalPageNoteList(
        {
          miniVisitorId: Number(router.params.id)
        },
        {
          pagination: {
            pageSize: 10,
            current: stateRef.current!.current
          },
          sort: {
            predicate: stateRef.current!.currentFilter === 1 ? "updatedTime" : "",
            reverse: stateRef.current!.currentFilter === 1
          },
          search: {}
        }
      )
    }
    Taro.showLoading({
      title: "加载中..."
    })
    action
      .then(res => {
        Taro.hideLoading()
        if (requestIsFullfilled(res)) {
          const { list, pagination } = res.data.data
          setState({
            list: pagination.current === 1 ? list : [...stateRef.current!.list, ...list],
            hasMore: pagination.current < pagination.pageCount
          })
        }
        isFetching.current = false
      })
      .catch(() => {
        Taro.hideLoading()
        isFetching.current = false
      })
  }
  function handleSwitchFilter(filter: number) {
    if (state.currentFilter === filter) return
    setState({ currentFilter: filter, current: 1 })
    fetchList()
  }
  function handleActionClick(noteItem: PrimaryKey<number>) {
    currentTargetRef.current = noteItem
    setState({ openAction: true })
  }
  function closeAction() {
    setState({ openAction: false })
  }
  function handleJumpEditInfo() {
    const fulfilled = () => navigation(pageMapperCommunity.EditPersonalInfo)
    authActionHandler(fulfilled, {
      mobile: true,
      avatarAndNickname: false
    })
  }
  function handleJumpFans() {
    if (!state.personalInfo.isSelf) return
    navigation(pageMapperCommunity.MyFans)
  }
  function handleSwitchConcern() {
    const hasFollowed = state.personalInfo.isFollowing
    concernPerson({ miniVisitorId: Number(router.params.id) }).then(res => {
      if (requestIsFullfilled(res)) {
        Taro.showToast({
          title: hasFollowed ? "已取消关注" : "关注成功",
          icon: "none"
        })
        const _personalInfo = Object.assign({}, state.personalInfo)
        _personalInfo.isFollowing = !hasFollowed
        setState({ personalInfo: _personalInfo })
      }
    })
  }
  function handleNoteLike(
    noteItem: PrimaryKey<number>,
    meta: IApiRelative.INoteLikeSwitch.IResData
  ) {
    const _list = stateRef.current!.list.concat()
    const finder = _list.find(l => l.id === noteItem.id)
    if (finder) {
      finder.isSelfLike = meta.isLike
      finder.likeCount = meta.likeCount
      setState({ list: _list })
    }
  }
  function handleActionSelect(action: typeof actions[number]) {
    if (!currentTargetRef.current) return
    const finder = stateRef.current!.list.find(l => l.id === currentTargetRef.current!.id)
    currentTargetRef.current = null
    if (!finder) {
      return
    }
    if (action.value == "edit") {
      // 跳转到编辑笔记
      navigation(pageMapperCommunity.NotePublish, {
        id: finder.id,
        topicId: finder.firstDiscussionId
      })
    } else if (action.value == "delete") {
      // 删除笔记
      Taro.showModal({
        content: "确定要删除该笔记吗？",
        success({ confirm }) {
          if (confirm) {
            removeMyNote({ id: finder.id }).then(res => {
              if (requestIsFullfilled(res)) {
                Taro.showToast({ title: "删除成功", icon: "none" })
                setState({ list: stateRef.current!.list.filter(l => l.id !== finder.id) })
              }
            })
          }
        }
      })
    }
  }
  function handleScroll({ detail }: { detail: ScrollViewProps.onScrollDetail }) {
    scrollHandler(detail.scrollTop)
  }
  function handleClickAccountName() {
    if (!state.personalInfo.isSelf && state.isAgency && state.personalInfo.agencyId) {
      navigation("school", { id: state.personalInfo.agencyId }, "navigateTo", true, true)
    }
  }
  function renderNavigation() {
    return (
      <GpNavbar
        className="absolute"
        navigationBarPlaceholder={false}
        navigationBarBackgroundColor={`rgba(255,255,255,${opacity})`}
        arrowLeftProps={{
          color:
            opacity < 0.5 ? `rgba(255, 255, 255, ${1 - opacity})` : `rgba(51, 51, 51, ${opacity})`
        }}
        onLayout={setLayout}
      />
    )
  }
  function renderActionBtns() {
    if (state.personalInfo.isSelf) {
      return (
        <React.Fragment>
          <View className={styles.editInfo} onClick={handleJumpEditInfo}>
            编辑资料
          </View>
          <View className={styles.share}>
            <GpShareButton shareText="分享" className={styles.shareBtn} />
          </View>
        </React.Fragment>
      )
    } else {
      const externalParam = {} as any
      if (state.personalInfo.sourceAgencyId) {
        externalParam.id = state.personalInfo.sourceAgencyId
      }
      return (
        <View className="flex flex-row items-center box-border ml-auto">
          {state.isAgency && (
            <View
              className={styles.consultBtn}
              onClick={() => navigation(pageMapper.external, externalParam)}
            >
              在线咨询
            </View>
          )}
          <View
            className={clsx(styles.concernBtn, {
              [styles.concerned]: state.personalInfo.isFollowing
            })}
            onClick={handleSwitchConcern}
          >
            {!state.personalInfo.isFollowing && (
              <Icon icon="icon-tianjia" color="#ffffff" size={16} />
            )}
            {state.personalInfo.isFollowing ? "已关注" : "关注"}
          </View>
        </View>
      )
    }
  }
  function renderBgInfo() {
    return (
      <NestedScrollHeader>
        <View
          className={styles.bgInfo}
          style={{
            backgroundImage: `url(${
              state.personalInfo.backgroundImage ||
              "https://csimg.91goodschool.com/UpFiles/gp/1000/202403/29/175944443332_w1280.png"
            })`
          }}
        >
          <View
            style={{
              position: "absolute",
              background: "linear-gradient(0deg, #353129 26.43%, #00000033 100%)",
              left: 0,
              top: 0,
              right: 0,
              bottom: 0,
              zIndex: 0
            }}
          ></View>
          <View
            className={styles.navBarPlaceholder}
            style={{
              height: layout.statusBarHeight + layout.navigationHeight + "px"
            }}
          ></View>
          <View className={styles.info}>
            <Image
              src={state.personalInfo.headImage || process.env.__DEF_AVATAR__}
              className={styles.avatar}
            />
            <View className={styles.infoDesc} onClick={handleClickAccountName}>
              <View
                className={styles.name}
                style={
                  state.skyline
                    ? {
                        display: "flex",
                        flexDirection: "row",
                        alignItems: "center"
                      }
                    : {}
                }
              >
                {state.personalInfo.nickName}
                {!state.personalInfo.isSelf && state.isAgency ? (
                  <Icon icon="icon-youjiantou" size={24} className="pl-4px" />
                ) : null}
              </View>
              {!state.personalInfo.isSelf && state.isAgency ? (
                <View className={styles.areaProject}>
                  <Image src="/images/yikao-community/renzheng.png" className={styles.agencyFlag} />
                  {state.personalInfo.agencyName}
                </View>
              ) : (
                <View className={styles.areaProject}>
                  {state.personalInfo.areaName}-{state.personalInfo.projectName}
                </View>
              )}
            </View>
          </View>
          {state.skyline ? (
            <Text className={styles.desc} overflow="ellipsis" maxLines={3}>
              {state.personalInfo.description || "这家伙很神秘，没有写个人简介"}
            </Text>
          ) : (
            <View className={clsx(styles.desc, "ellipse_3")}>
              {state.personalInfo.description || "这家伙很神秘，没有写个人简介"}
            </View>
          )}
          <View className={styles.actions}>
            <View className={styles.fans} onClick={handleJumpFans}>
              {state.personalInfo.followerCount}粉丝
            </View>
            <View className={styles.zan}>
              {state.personalInfo.receivedLikeCount + state.personalInfo.receivedCollectCount}
              赞与收藏
            </View>
            {renderActionBtns()}
          </View>
          {/* skyline层级问题, 导致filter面板圆角部分出不来，故模拟filter面板顶部部分 */}
          {state.skyline && (
            <View
              style={{
                position: "absolute",
                background: "#ffffff",
                left: 0,
                bottom: -2,
                right: 0,
                zIndex: 0,
                height: "16px",
                borderRadius: "16px 16px 0 0"
              }}
            ></View>
          )}
        </View>
      </NestedScrollHeader>
    )
  }
  function renderFilters() {
    return (
      <NestedScrollHeader>
        <StickySection>
          <StickyHeader>
            {/* skyline模式下不支持margin-left为负数, 所以用top替代 */}
            <View
              className={clsx(
                styles.content,
                state.skyline ? styles.skylineContent : styles.webviewContent
              )}
            >
              <View
                className={clsx(styles.contentTabs, {
                  [styles.zuirezuixin]: !state.personalInfo.isSelf
                })}
              >
                {tabFilters.current.map(l => (
                  <View
                    className={clsx(styles.contentTab, {
                      [styles.contentTab__active]: state.currentFilter === l.value
                    })}
                    key={l.value}
                    onClick={() => handleSwitchFilter(l.value)}
                  >
                    {l.label}
                  </View>
                ))}
              </View>
            </View>
          </StickyHeader>
        </StickySection>
      </NestedScrollHeader>
    )
  }
  function renderUnknown() {
    if (state.list.length > 0) {
      // 仅当是自己的笔记 才出现操作action面板
      const showActionFlag = state.personalInfo.isSelf && state.currentFilter === 0
      return (
        <ScrollView
          scrollY
          type="custom"
          associativeContainer="nested-scroll-view"
          showScrollbar={false}
          className={clsx(styles.noteList, {
            [styles.webviewNoteList]: !state.skyline
          })}
          onScrollToLower={handleReachBottom}
        >
          <GridView type="masonry" crossAxisCount={2} crossAxisGap={5} mainAxisGap={5}>
            {state.list.map(l => (
              <GpNoteItem
                skyline={state.skyline}
                key={l.id}
                onAction={handleActionClick}
                noteItem={{
                  id: l.id,
                  actionFlag: showActionFlag,
                  avatar: l.createdByHead,
                  fileType: l.fileType,
                  image: l.thumbnail,
                  liked: l.isSelfLike,
                  likes: l.likeCount,
                  name: l.createdByName,
                  title: l.title,
                  videoFlag: !showActionFlag,
                  content: l.description,
                  auditFlag: showActionFlag,
                  auditStatusJson: showActionFlag ? l.auditStatusJson : null
                }}
                onLike={handleNoteLike}
              />
            ))}
          </GridView>
        </ScrollView>
      )
    } else {
      let src = "https://static.91goodschool.com/UpFiles/public/yikao/image/shou.png"
      let description = "你还没有发布过任何笔记哦"
      if (stateRef.current!.personalInfo.isSelf) {
        // 自己主页, filters: 我的笔记和我收藏的笔记
        if (stateRef.current!.currentFilter !== 0) {
          // 我收藏的笔记
          src = "https://static.91goodschool.com/UpFiles/public/yikao/image/shu.png"
          description = "你还没有收藏过任何笔记哦"
        }
      } else {
        // 他人主页, filters: 最热笔记和最新笔记
        description = "TA还没有发布过任何笔记哦"
      }
      return (
        <GpEmpty
          imageProps={{
            src,
            style: {
              width: 126,
              height: 112
            }
          }}
          emptyProps={{
            style: {
              paddingTop: 120
            }
          }}
          description={description}
        />
      )
    }
  }
  function renderContentNotes() {
    return (
      <NestedScrollBody>
        <View
          style={{
            width: "100%",
            height: "100%"
          }}
        >
          {renderUnknown()}
        </View>
      </NestedScrollBody>
    )
  }
  return (
    <GpContainer
      className="h-full min-h-screen"
      style={{
        backgroundColor: "#F7F7F7"
      }}
      shareConfig={{
        title: "我的主页-" + state.personalInfo.nickName
      }}
    >
      {renderNavigation()}
      <ScrollView
        type="nested"
        scrollY
        showScrollbar={false}
        style={{
          width: "100%",
          height: "100%"
        }}
        onScroll={handleScroll}
      >
        {renderBgInfo()}
        {renderFilters()}
        {renderContentNotes()}
      </ScrollView>
      <GpActionSheet
        open={state.openAction}
        closeFn={closeAction}
        actions={actions}
        onSelect={handleActionSelect}
      />
    </GpContainer>
  )
}
